/** 
 * \file projections.h
 *       Filename:  projections.h
 * =====================================================================================
 * 
 *    Description:  Définition of cartographic projections
 * 
 *        Version:  1.0
 *        Created:  11/11/2009 15:04:01
 *       Revision:  none
 *       Compiler:  gcc
 * 
 *         Author:  François Hissel (fh), francois.hissel@m4x.org
 *        Company:  
 * 
 * =====================================================================================
 */

#ifndef  PROJECTIONS_H_INC
#define  PROJECTIONS_H_INC

/**
 * \brief Converts an angle in degrees, minutes and seconds in its radian value
 *
 * This function computes the value of the angle in radian from its value in degrees, minutes and seconds.
 * \param deg Degrees
 * \param min Minutes
 * \param sec Seconds
 * \return Value in radians
 */
double convert_angle(double deg,double min,double sec);

/**
 * \brief Molodensky transform, converts geographical coordinates from one geodetic system to another
 *
 * This function applies the Molodensky transform, which converts geographical coordinates between two geodesic systems.
 * The formula used are the following:
 * \f[
 * \lambda_2=\lambda_1+\frac{-T_X\sin\lambda_1+T_Y\cos\lambda_1}{N\cos\phi_1}
 * \phi_2=\phi_1+\frac{-T_X\sin\phi_1\cos\lambda_1-T_y\sin\phi_1\sin\lambda_1+T_Z\cos\phi_1+(a\Delta f+f\Delta a)sin(2\phi_1)}{\rho}
 * \f]
 * with \f$(\lambda_1,\phi_1)\f$ and \f$(\lambda_2,\phi_2)\f$ the coordinates of the same point (longitude, latitude) in the old new systems, $a_i,f_i$ the length of the long axis and the eccentricity of the ellipsoid, \f$\Delta a=a_2-a_1\$, \f$\Delta f=f_2-f_1\f$, \f$T_X,T_Y,T_Z\f$ the parameters of the transform, and \f$N\f$, \f$\rho\f$, defined as follow:
 * \f[
 * e=\sqrt{2f-f^2}
 * N=\frac{a}{\sqrt{1-e^2\sin^2\phi}}
 * \rho==\frac{a(1-e^2)}{\left(1-e^2\sin^2\phi\right)^{\frac{3}{2}}}
 * \f]
 * \param a First coordinate of the point in the old system
 * \param b Second coordinate of the point in the old system
 * \param x Pointer to the first coordinate of the point in the new system
 * \param y Pointer to the second coordinate of the point in the new system
 * \param params Set of parameters to use for calculation. The array shall hold 7 double values, in the following order: \f$a_1,f_1,a_2,f_2,T_X,T_Y,T_Z\f$.
 * 
 */
void _molodensky(double u,double v,double *x,double *y,double *params);

/**
 * \brief Molodensky transform, for particular cases of conversion
 *
 * This function applies a Molodensky transform by using internal parameters.
 * \param a First coordinate of the point in the old system
 * \param b Second coordinate of the point in the old system
 * \param x Pointer to the first coordinate of the point in the new system
 * \param y Pointer to the second coordinate of the point in the new system
 * \param code Code of the transform to apply. The following codes are used now:
 * 	- 0 : transform from Clarke ellipsoid geodetic system (NTF) to WGS84 system
 * 	- 1 : transform from WGS84 system to Clarke ellipsoid geodetic system (NTF)
 */
void molodensky(double u,double v,double *x,double *y,char code);

/**
 * \brief Converts spherical coordinates (longitude,latitude) into Lambert conformical conic projection coordinates
 *
 * This function computes the coordinates of the Lambert conformical conic projection from the spherical coordinates of a point on the surface of the Earth. Different parameters can be used, according to the center of the projection and are given as argument params. a and b are the spherical coordinates of the point, and x and y are references to doubles where the results will be stored.
 * The following formulas are used to compute the projected coordinates:
 * \f[ \left\{\begin{array}{lll}
 * e & = & \sqrt{\frac{\alpha^2+\beta^2}{\alpha^2}}\\
 * \nu & = & \frac{1}{2}\ln\frac{1+\sin\phi}{1-\sin\phi}-\frac{e}{2}\ln\frac{1+e\sin\phi}{1-e\sin\phi} \\
 * R & = & C \exp(-n\nu)\\
 * \gamma & = & n(\lambda-\lambda_0)\\
 * \end{array}\right.\f]
 * With the previous values calculates, it is now possible to evaluate the coordinates:
 * \f[ \left\{\begin{array}{lll}
 * x & = & x_0+R\sin\gamma\\
 * y & = & y_0-R\cos\gamma\\
 * \end{array}\right.\f]
 * where \f$(\lambda,\phi)\f$ are the spherical coordinates (longitude, latitude) of the location, and \f$\alpha,\beta,n,C,x_0,y_0\f$ are parameters which values can be found in tables and depend on the location of the center of the projection.
 * \param a Longitude of the point
 * \param b Latitude of the point
 * \param x First coordinate of the point in a Lambert conformical conic projection
 * \param y Second coordinate of the point in a Lambert conformical conic projection
 * \param params Set of parameters to use for calculation. The array shall hold 7 double values, in the following order: \f$\alpha,\beta,\lambda_0,n,C,x_0,y_0\f$.
 */
void _lambert(double a,double b,double *x,double *y,double *params);

/**
 * \brief Converts spherical coordinates (longitude, latitude) into Lambert conformical conic projection coordinates, using a standard system of projection on the French territory
 *
 * This function computes the coordinates of the Lambert conformical conic projection from the spherical coordinates of a point on the surface of the Earth. It uses one of the standard system on the French territory.
 * The parameter code can take the following values:
 * 	- 0 Lambert 93
 * 	- 1 Lambert I (North)
 * 	- 2 Lambert II (Center)
 * 	- 3 Lambert III (South)
 * 	- 4 Lambert IV (Corse)
 * 	- 5 Lambert II extended
 * \param a Longitude of the point
 * \param b Latitude of the point
 * \param x First coordinate of the point in a Lambert conformical conic projection
 * \param y Second coordinate of the point in a Lambert conformical conic projection
 * \param code Code of the standard system
 */
void lambert(double a,double b,double *x,double *y,char code);

/**
 * \brief Converts geographical coordinates from a WGS84 geodetic system to plane coordinates in a Lambert conformical conic projection, using a NTF geodetic system. The new projection matches the French standard Lambert II extended.
 *
 * This function uses the previously defines functions to convert directly geographical coordinates to planar ones and changes the geodetic system.
 * \param a Longitude of the point
 * \param b Latitude of the point
 * \param x First coordinate of the point in a Lambert conformical conic II extended projection
 * \param y Second coordinate of the point in a Lambert conformical conic II extended projection
 */
void projection(double a,double b,double *x,double *y);

#endif   // ----- #ifndef PROJECTIONS_H_INC  -----
